package com.jy.project.service.imp;

import com.alibaba.fastjson.JSONObject;
import com.jy.project.constant.MaterialConstant;
import com.jy.project.controller.ApplyController;
import com.jy.project.controller.MatericalController;
import com.jy.project.domain.*;
import com.jy.project.dto.*;
import com.jy.project.enums.ApplyTypeEnum;
import com.jy.project.enums.ApplyTypeMatericalEnum;
import com.jy.project.enums.QualityStatusEnum;
import com.jy.project.ex.BizException;
import com.jy.project.mapper.*;
import com.jy.project.service.ApplyService;
import com.jy.project.service.imp.defult.DefaultApplyBusinessImp;
import com.jy.project.util.*;
import com.jy.project.vo.ApplyDeptAdminVO;
import com.jy.project.vo.ApplyQualitVO;
import com.jy.project.vo.ApplyUserVO;
import com.jy.project.vo.MaterialVO;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.DateUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
import org.springframework.stereotype.Service;
import org.springframework.transaction.TransactionDefinition;
import org.springframework.transaction.TransactionStatus;
import org.springframework.util.CollectionUtils;
import tk.mybatis.mapper.entity.Example;

import java.util.*;

@Service("applyBorrowServiceImpl")
@Slf4j
public class ApplyBorrowServiceImpl extends DefaultApplyBusinessImp implements ApplyService {

    @Autowired
    private ApplyMapper applyMapper;

    @Autowired
    private UserMapper userMapper;

    @Autowired
    private MaterialMapper materialMapper;

    @Autowired
    private ApplyBorrowMapper applyBorrowMapper;


    @Autowired
    private RedisUtils redisUtils;

    @Autowired
    DataSourceTransactionManager dataSourceTransactionManager;

    @Autowired
    TransactionDefinition transactionDefinition;


    @Override
    public boolean insertApply(ApplyDTO dto) {
        dto.setApplyType(ApplyTypeEnum.BORROW.getCode());
        Set<Integer> set = new HashSet<>();
        set.add(dto.getApplyType());
        dto.setExt(JSONObject.toJSONString(set));
        TransactionStatus transactionStatus = dataSourceTransactionManager.getTransaction(transactionDefinition);
        try {
            boolean bl = this.insertApplyBusiness(dto);
            if (bl == false) {
                throw new BizException("申请借用失败");
            }
        }catch (Exception e){
            dataSourceTransactionManager.rollback(transactionStatus);
            throw  e;
        }
        dataSourceTransactionManager.commit(transactionStatus);
        return true;
    }

    @Override
    public List<ApplyQualitVO> listApplyQualityVO(ApplyQueryDTO dto) {

        return applyMapper.listApplyyQualityVO(dto);
    }

    @Override
    public List<ApplyDeptAdminVO> listDeptAdminApplyVO(ApplyDeptAdminQueryDTO dto) {
        return null;
    }

    @Override
    public boolean applyAdopt(ApplyAdoptDTO dto) {
        log.info("审批通过外借单");
        String applyNo = dto.getApplyNo();
        Apply apply = applyMapper.getApplyByApplyNo(applyNo);
        if (apply==null){
            throw  new BizException("申请单不存在");
        }
        Example example =new Example(ApplyBorrow.class);
        example.createCriteria().andEqualTo("applyNo",applyNo);
        List<ApplyBorrow> applyBorrows = applyBorrowMapper.selectByExample(example);
        if (CollectionUtils.isEmpty(applyBorrows)){
            throw  new BizException("数据不存在");
        }
        List<String> materialNos=new ArrayList<>();
        for (int i = 0; i < applyBorrows.size(); i++) {
            materialNos.add(applyBorrows.get(i).getMaterialNo());
        }
        ApplyUpdateDTO applyUpdateCollectDTO=new ApplyUpdateDTO();
        BeanUtils.copyProperties(apply,applyUpdateCollectDTO);
        String s = CommonStringUtils.toStr(materialNos);
        applyUpdateCollectDTO.setMaterialNos(s);
        applyUpdateCollectDTO.setUseStatus(1);
        return materialMapper.updateApplyUpdateCollectDTO(applyUpdateCollectDTO)>0;
    }

    @Override
    public boolean applyReject(ApplyAdoptDTO dto) {
        log.info("驳回通过外借单");
        return true;
    }

    @Override
    public ServiceResultUtils listMaterialDetailsVO(MaterialDetailsDTO dto) {
       return  null;
    }

    @Override
    public List<ApplyUserVO> listUserApplyVO(ApplyUserQueryDTO dto) {
        return null;
    }


    @Override
    public void checkApplyNo(String applyNo) {
        super.checkApplyNo(applyNo);
    }

    @Override
    public MaterialVO checkMaterialNo(String materialNo) {
        return super.checkMaterialNo(materialNo);
    }

    @Override
    public boolean insertApplyBusiness(ApplyDTO dto) {
        if (dto==null){
            throw new BizException("Apply对象为空");
        }
        checkApplyNo(dto.getApplyNo());

        //制单人
        String token = dto.getToken();
        User u = JwtUtils.verifyToken(token);
        Long id = u.getId();
        User user = userMapper.selectByPrimaryKey(id);
        if (user==null){
            throw  new BizException("用户信息可能找不到");
        }
        String[] checkMaterialNos = dto.getCheckMaterialNos();
        if (checkMaterialNos==null){
            throw  new BizException("没有选中信息");
        }
        if (checkMaterialNos.length<0){
            throw  new BizException("没有选中信息");
        }
        List<MaterialVO> materialVOS = checkMaterialNos(checkMaterialNos);
        if (materialVOS.isEmpty()){
            throw  new BizException("当前编号资产找不到,或为无法使用状态");
        }
        ApplyBorrowDTO applyBorrowDTO=(ApplyBorrowDTO)dto;
        String returnDate = applyBorrowDTO.getReturnDate();
        if (StringUtils.isEmpty(returnDate)){
            throw  new BizException("归还日期不能为空");
        }
        Date date =new Date();
        try {
            date=DateUtils.parseDate(returnDate, "yyyy-MM-dd");
        }catch (Exception e){
            throw  new BizException("归还日期格式错误");
        }
        for (int i = 0; i < materialVOS.size(); i++) {
            Apply ay = this.create();
            ay.setApplyNo(CodeUtils.generateApplyNo(ApplyTypeMatericalEnum.BORROW.getValue()));
            ay.setApplyType(dto.getApplyType());
            ay.setName(ApplyTypeEnum.getValue(ay.getApplyType()));
            ay.setApplicantCompanyNo(user.getCompanyNo());
            ay.setApplicantCompanyName(user.getCompanyName());
            ay.setApplicantDeptNo(user.getDeptNo());
            ay.setApplicantDeptName(user.getDeptName());
            ay.setApplicantUserId(user.getId());
            ay.setApplicantUserNickName(user.getNickName());
            Long useUserId = dto.getUseUserId();
            //使用人
            if (useUserId!=null&&useUserId!=0){
                User useUser = userMapper.selectByPrimaryKey(dto.getUseUserId());
                if (useUser==null){
                    throw  new BizException("使用者用户信息找不到");
                }
                ay.setUseCompanyNo(useUser.getCompanyNo());
                ay.setUseCompanyName(useUser.getCompanyName());
                ay.setUseDeptNo(useUser.getDeptNo());
                ay.setUseDeptName(useUser.getDeptName());
                ay.setUseUserId(useUser.getId());
                ay.setUseNickName(useUser.getNickName());
            }
            ay.setExt(dto.getExt());
            ay.setRemarks(dto.getRemarks());
            MaterialVO materialVO = materialVOS.get(i);
            ApplyBorrow applyBorrow=new ApplyBorrow();
            BeanUtils.copyProperties(ay,applyBorrow);
            applyBorrow.setMaterialName(materialVO.getName());
            applyBorrow.setStatus(0);
            applyBorrow.setImg(materialVO.getImg());
            applyBorrow.setReturnDate(date);
            applyBorrow.setLatestReturnDate(date);
            String materialNo = materialVO.getMaterialNo();
            applyBorrow.setMaterialNo(materialNo);
            ay.setApplyNo(materialNo);
            applyBorrowMapper.insertSelective(applyBorrow);
            applyMapper.insertSelective(ay);
        }
        return true;
    }

    private  List<MaterialVO> checkMaterialNos(String[] split ){
        String s = CommonStringUtils.toStrNotQuotationMarks(split);
        List<MaterialVO> materialVOS = materialMapper.listMaterialVOByMaterialNos(s);

        for (int i = 0; i < materialVOS.size(); i++) {
            MaterialVO materialVO = materialVOS.get(i);
            if (materialVO.getUseStatus()!=0){
                throw  new BizException("编号["+materialVO.getMaterialNo()+"]资产不是闲置状态");
            }
            String[] qualityStatus = materialVO.getQualityStatus();
            if (qualityStatus!=null ||qualityStatus.length>0){
                boolean bl=false;
                for (int j = 0; j < qualityStatus.length; j++) {
                    String qStatus = qualityStatus[j];
                    if (qStatus.equals(QualityStatusEnum.LOANABLE.getCode().toString())){
                        bl=true;
                    }
                }
                if (bl==false){
                    throw  new BizException("编号["+materialVO.getMaterialNo()+"]资产质量状态设置不可领取");
                }
            }

        }
        return  materialVOS;
    }

}
